﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using Microsoft.Win32;

namespace Movistar.SMS.OutlookAddIn
{
    public partial class ConfigForm : Form
    {
        private RemindersDB remindersDB = null;
        private enum tabStatusCollection { Initializing, NormalEmpty, NormalSelected, Creating, Modifying };
        private tabStatusCollection currentTemplateStatus = tabStatusCollection.Initializing;
        private tabStatusCollection currentReminderStatus = tabStatusCollection.Initializing;
        private tabStatusCollection currentSettingsStatus = tabStatusCollection.NormalEmpty;

        #region Form Open Close Events

        public ConfigForm()
        {
            InitializeComponent();

            try
            {
                RegistryKey key = Registry.LocalMachine.OpenSubKey(OutlookAddIn.Properties.Settings.Default.RegKeyAddIn);

                remindersDB = new RemindersDB(key.GetValue(OutlookAddIn.Properties.Settings.Default.RegKeyDB).ToString());

                LoadTemplateNames(null);
                LoadReminderNames(null);
                LoadSettings();
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }
        }

        private void btOk_Click(object sender, EventArgs e)
        {
            DialogResult = DialogResult.OK;
        }

        private void SetupForm_FormClosing(object sender, FormClosingEventArgs e)
        {
            if (DialogResult == DialogResult.Abort) // If any arror just close and propagate error to caller
                return;

            if ((currentTemplateStatus == tabStatusCollection.Creating) || (currentTemplateStatus == tabStatusCollection.Modifying) ||
                (currentReminderStatus == tabStatusCollection.Creating) || (currentReminderStatus == tabStatusCollection.Modifying) ||
                (currentSettingsStatus == tabStatusCollection.Modifying))
            {
                DialogResult res = MessageBox.Show("Hay cambios sin guardar. ¿Está seguro de que desea salir?",
                    "Configuración Movistar SMS", MessageBoxButtons.YesNo, MessageBoxIcon.Exclamation);

                if (res == DialogResult.No)
                {
                    e.Cancel = true;

                    if ((currentTemplateStatus == tabStatusCollection.Creating) || (currentTemplateStatus == tabStatusCollection.Modifying))
                        edTemplateName.Focus();
                    else if ((currentReminderStatus == tabStatusCollection.Creating) || (currentReminderStatus == tabStatusCollection.Modifying))
                        edReminderName.Focus();
                    else if (currentSettingsStatus == tabStatusCollection.Modifying)
                        edServiceURL.Focus();
                }
            }
        }
        #endregion

        #region Templates TAB

        private void btNewTemplate_Click(object sender, EventArgs e)
        {
            SetTemplatesStatus(tabStatusCollection.Creating);

            edTemplateName.Focus();
        }

        private void btModifyTemplate_Click(object sender, EventArgs e)
        {
            SetTemplatesStatus(tabStatusCollection.Modifying);

            edTemplateText.Focus();
        }

        private void btEraseTemplate_Click(object sender, EventArgs e)
        {
            try
            {
                Templates currentTemplate = (from t in remindersDB.Templates
                                             where t.Name == lbTemplates.SelectedItem.ToString()
                                             select t).Single();

                var appointmentsInUse = (from ap in remindersDB.Appointments
                                         where ap.TemplateID_ == currentTemplate.TemplateID_
                                         select ap);

                if (appointmentsInUse.Count() > 0)
                {
                    MessageBox.Show("Esa plantilla está en uso en multiples citas, no puede eliminarse.", "Configuración Movistar SMS",
                        MessageBoxButtons.OK, MessageBoxIcon.Exclamation);

                    return;
                }

                remindersDB.Templates.DeleteOnSubmit(currentTemplate);

                remindersDB.SubmitChanges();
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }

            LoadTemplateNames(null);
        }

        private void btCancelTemplate_Click(object sender, EventArgs e)
        {
            if (lbTemplates.Items.Count > 0)
                lbTemplates_SelectedValueChanged(lbTemplates, null);
            else
                SetTemplatesStatus(tabStatusCollection.NormalEmpty);
        }

        private void btSaveTemplate_Click(object sender, EventArgs e)
        {
            if (edTemplateName.Text.Trim().Length == 0)
            {
                MessageBox.Show("Debe introducir algún nombre para la plantilla.", "Configuración Movistar SMS",
                    MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                return;
            }

            if (edTemplateText.Text.Trim().Length == 0)
            {
                MessageBox.Show("Debe introducir algún texto para la plantilla.", "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                return;
            }

            try
            {
                if (currentTemplateStatus == tabStatusCollection.Creating)
                {
                    var existingTemplates = from t in remindersDB.Templates
                                            where t.Name == edTemplateName.Text.Trim()
                                            select t;

                    if (existingTemplates.Count() > 0)
                    {
                        MessageBox.Show("Ya existe otra plantilla con ese nombre.", "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                        return;
                    }

                    Templates newTemplate = new Templates() { Name = edTemplateName.Text.Trim(), Text = edTemplateText.Text.Trim() };

                    remindersDB.Templates.InsertOnSubmit(newTemplate);

                    remindersDB.SubmitChanges();
                }
                else if (currentTemplateStatus == tabStatusCollection.Modifying)
                {
                    Templates currentTemplate = (from t in remindersDB.Templates
                                                 where t.Name == lbTemplates.SelectedItem.ToString()
                                                 select t).Single();

                    if (lbTemplates.SelectedItem.ToString() != edTemplateName.Text.Trim()) // Template Name Changed
                    {
                        var existingTemplates = from t in remindersDB.Templates
                                                where t.Name == edTemplateName.Text.Trim() && t.TemplateID_ != currentTemplate.TemplateID_
                                                select t;

                        if (existingTemplates.Count() > 0)
                        {
                            MessageBox.Show("Ya existe otra plantilla con ese nombre.", "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                            return;
                        }
                    }

                    currentTemplate.Name = edTemplateName.Text.Trim();
                    currentTemplate.Text = edTemplateText.Text.Trim();

                    remindersDB.SubmitChanges();
                }
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }

            LoadTemplateNames(edTemplateName.Text);
        }

        private void LoadTemplateNames(string selectedTemplateName)
        {
            int _selectedIndex = 0;

            lbTemplates.Items.Clear();

            try
            {
                var templateNames = from templates in remindersDB.Templates
                                    select templates;

                foreach (var template in templateNames)
                {
                    if (template.Name == selectedTemplateName)
                        _selectedIndex = lbTemplates.Items.Add(template.Name);
                    else
                        lbTemplates.Items.Add(template.Name);
                }

                if (lbTemplates.Items.Count == 0)
                    SetTemplatesStatus(tabStatusCollection.NormalEmpty);
                else
                    lbTemplates.SelectedIndex = _selectedIndex;  // SelectedValueChanged is fired here
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }
        }

        private void lbTemplates_SelectedValueChanged(object sender, EventArgs e)
        {
            try
            {
                Templates template = (from t in remindersDB.Templates
                                      where t.Name == lbTemplates.SelectedItem.ToString()
                                      select t).Single();

                edTemplateName.Text = template.Name;
                edTemplateText.Text = template.Text;
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }

            SetTemplatesStatus(tabStatusCollection.NormalSelected);
        }

        private void SetTemplatesStatus(tabStatusCollection status)
        {
            if (status == currentTemplateStatus)
                return;

            lbTemplates.Enabled = status == tabStatusCollection.NormalSelected;
            btNewTemplate.Enabled = (status == tabStatusCollection.NormalEmpty) || (status == tabStatusCollection.NormalSelected);
            btModifyTemplate.Enabled = (status == tabStatusCollection.NormalSelected);
            btEraseTemplate.Enabled = (status == tabStatusCollection.NormalSelected);
            edTemplateName.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);
            edTemplateText.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);
            btSaveTemplate.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);
            btCancelTemplate.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);

            if ((status == tabStatusCollection.Creating) || (status == tabStatusCollection.NormalEmpty))
            {
                edTemplateName.Text = "";
                edTemplateText.Text = "";
            }

            currentTemplateStatus = status;
        }

        #endregion

        #region Reminders TAB

        private void btNewReminder_Click(object sender, EventArgs e)
        {
            SetReminderStatus(tabStatusCollection.Creating);

            edReminderName.Focus();
        }

        private void btModifyReminder_Click(object sender, EventArgs e)
        {
            SetReminderStatus(tabStatusCollection.Modifying);

            edReminderDays.Focus();
        }

        private void btEraseReminder_Click(object sender, EventArgs e)
        {
            try
            {
                Reminders currentReminder = (from t in remindersDB.Reminders
                                             where t.Name == lbReminders.SelectedItem.ToString()
                                             select t).Single();

                var appointmentsInUse = (from ap in remindersDB.AppointmentReminders
                                         where ap.ReminderID_ == currentReminder.ReminderID_
                                         select ap);

                if (appointmentsInUse.Count() > 0)
                {
                    MessageBox.Show("Esa programación está en uso en multiples citas, no puede eliminarse.",
                        "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);

                    return;
                }

                remindersDB.Reminders.DeleteOnSubmit(currentReminder);

                remindersDB.SubmitChanges();
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }

            LoadReminderNames(null);
        }

        private void btCancelReminder_Click(object sender, EventArgs e)
        {
            if (lbReminders.Items.Count > 0)
                lbReminders_SelectedValueChanged(lbReminders, null);
            else
                SetReminderStatus(tabStatusCollection.NormalEmpty);
        }

        private void btSaveReminder_Click(object sender, EventArgs e)
        {
            if (edReminderName.Text.Trim().Length == 0)
            {
                MessageBox.Show("Debe introducir algún nombre para la programación.", "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                return;
            }

            if ((edReminderDays.Text.Trim().Length == 0) || (edReminderHours.Text.Trim().Length == 0) || (edReminderMinutes.Text.Trim().Length == 0))
            {
                MessageBox.Show("Debe introducir todos los datos de la programación.", "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                return;
            }

            try
            {
                if (currentReminderStatus == tabStatusCollection.Creating)
                {
                    var existingReminders = from t in remindersDB.Reminders
                                            where t.Name == edReminderName.Text.Trim()
                                            select t;

                    if (existingReminders.Count() > 0)
                    {
                        MessageBox.Show("Ya existe otra programación con ese nombre.", "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                        return;
                    }

                    Reminders newReminder = new Reminders()
                    {
                        Name = edReminderName.Text.Trim(),
                        Days = short.Parse(edReminderDays.Text.Trim()),
                        Hours = short.Parse(edReminderHours.Text.Trim()),
                        Minutes = short.Parse(edReminderMinutes.Text.Trim())
                    };

                    remindersDB.Reminders.InsertOnSubmit(newReminder);

                    remindersDB.SubmitChanges();
                }
                else if (currentReminderStatus == tabStatusCollection.Modifying)
                {
                    Reminders currentReminder = (from t in remindersDB.Reminders
                                                 where t.Name == lbReminders.SelectedItem.ToString()
                                                 select t).Single();

                    if (lbReminders.SelectedItem.ToString() != edReminderName.Text.Trim()) // Reminder Name Changed
                    {
                        var existingReminders = from t in remindersDB.Reminders
                                                where t.Name == edReminderName.Text.Trim() && t.ReminderID_ != currentReminder.ReminderID_
                                                select t;

                        if (existingReminders.Count() > 0)
                        {
                            MessageBox.Show("Ya existe otra programación con ese nombre.", "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                            return;
                        }
                    }

                    currentReminder.Name = edReminderName.Text.Trim();
                    currentReminder.Days = short.Parse(edReminderDays.Text.Trim());
                    currentReminder.Hours = short.Parse(edReminderHours.Text.Trim());
                    currentReminder.Minutes = short.Parse(edReminderMinutes.Text.Trim());

                    remindersDB.SubmitChanges();
                }
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }

            LoadReminderNames(edReminderName.Text);
        }

        private void edNumericField_KeyPress(object sender, KeyPressEventArgs e)
        {
            if (!((e.KeyChar == (char)8) || ((e.KeyChar >= (char)'0') && (e.KeyChar <= (char)'9'))))
                e.KeyChar = (char)0;
        }

        private void edNumerifField_Validating(object sender, CancelEventArgs e)
        {
            if (((TextBox)sender).Text.Length == 0)
                ((TextBox)sender).Text = "0";

            int _maxValue = 0;

            if (sender == edReminderDays)
                _maxValue = 365;
            else if (sender == edReminderHours)
                _maxValue = 24;
            else if (sender == edReminderMinutes)
                _maxValue = 60;

            try
            {
                if (short.Parse(((TextBox)sender).Text) > _maxValue)
                    ((TextBox)sender).Text = _maxValue.ToString();

                ((TextBox)sender).Text = short.Parse(((TextBox)sender).Text).ToString();
            }
            catch
            {
                ((TextBox)sender).Text = _maxValue.ToString();
            }
        }

        private void LoadReminderNames(string selectedReminderName)
        {
            int _selectedIndex = 0;

            lbReminders.Items.Clear();

            try
            {
                var reminderNames = from reminders in remindersDB.Reminders
                                    select reminders;

                foreach (var reminder in reminderNames)
                {
                    if (reminder.Name == selectedReminderName)
                        _selectedIndex = lbReminders.Items.Add(reminder.Name);
                    else
                        lbReminders.Items.Add(reminder.Name);
                }

                if (lbReminders.Items.Count == 0)
                    SetReminderStatus(tabStatusCollection.NormalEmpty);
                else
                    lbReminders.SelectedIndex = _selectedIndex; // SelectedValueChanged is fired here
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }
        }

        private void lbReminders_SelectedValueChanged(object sender, EventArgs e)
        {
            try
            {
                Reminders reminder = (from t in remindersDB.Reminders
                                      where t.Name == lbReminders.SelectedItem.ToString()
                                      select t).Single();

                edReminderName.Text = reminder.Name;
                edReminderDays.Text = reminder.Days.ToString();
                edReminderHours.Text = reminder.Hours.ToString();
                edReminderMinutes.Text = reminder.Minutes.ToString();

            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }

            SetReminderStatus(tabStatusCollection.NormalSelected);
        }

        private void SetReminderStatus(tabStatusCollection status)
        {
            if (status == currentReminderStatus)
                return;

            lbReminders.Enabled = status == tabStatusCollection.NormalSelected;
            btNewReminder.Enabled = (status == tabStatusCollection.NormalEmpty) || (status == tabStatusCollection.NormalSelected);
            btModifyReminder.Enabled = (status == tabStatusCollection.NormalSelected);
            btEraseReminder.Enabled = (status == tabStatusCollection.NormalSelected);
            edReminderName.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);
            edReminderDays.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);
            edReminderHours.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);
            edReminderMinutes.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);
            btSaveReminder.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);
            btCancelReminder.Enabled = (status == tabStatusCollection.Creating) || (status == tabStatusCollection.Modifying);

            if ((status == tabStatusCollection.Creating) || (status == tabStatusCollection.NormalEmpty))
            {
                edReminderName.Text = "";
                edReminderDays.Text = "0";
                edReminderHours.Text = "0";
                edReminderMinutes.Text = "0";
            }

            currentReminderStatus = status;
        }

        #endregion

        #region Settings TAB

        public void LoadSettings()
        {
            edServiceURL.Text = LoadSetting("SERVICEURL");
            edServiceMobile.Text = LoadSetting("SERVICEMOBILE");
            edServicePass.Text = LoadSetting("SERVICEPASS");

            currentSettingsStatus = tabStatusCollection.NormalEmpty;
            btModifySaveSettings.Text = "&Modificar";
            edServiceURL.Enabled = false;
            edServiceMobile.Enabled = false;
            edServicePass.Enabled = false;
        }

        private void btModifySaveSettings_Click(object sender, EventArgs e)
        {
            if (currentSettingsStatus == tabStatusCollection.NormalEmpty)
            {
                currentSettingsStatus = tabStatusCollection.Modifying;
                btModifySaveSettings.Text = "&Guardar";
                edServiceMobile.Enabled = true;
                edServicePass.Enabled = true;
                edServiceURL.Enabled = true;
            }
            else if (currentSettingsStatus == tabStatusCollection.Modifying)
            {
                if ((edServiceURL.Text.Length == 0) || (edServicePass.Text.Length == 0) || (edServiceMobile.Text.Length < 9))
                {
                    MessageBox.Show("Debe rellenar todos los campos solicitados para una configuración correcta.",
                            "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Question);
                }
    
                SaveSetting("SERVICEURL", edServiceURL.Text.Trim());
                SaveSetting("SERVICEMOBILE", edServiceMobile.Text.Trim()); 
                SaveSetting("SERVICEPASS", edServicePass.Text.Trim());

                currentSettingsStatus = tabStatusCollection.NormalEmpty;
                btModifySaveSettings.Text = "&Modificar";
                edServiceMobile.Enabled = false;
                edServicePass.Enabled = false;
                edServiceURL.Enabled = false;
            }
        }

        private string LoadSetting(string sKey)
        {
            try
            {
                var value = from setting in remindersDB.Settings
                            where setting.Key == sKey
                            select setting;

                if (value.Count() > 0)
                    return (value.Single().Value);
                else
                {
                    Settings newSetting = new Settings() { Key = sKey, Value = "" };

                    remindersDB.Settings.InsertOnSubmit(newSetting);
                    remindersDB.SubmitChanges();
                }
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }

            return ("");
        }

        private void SaveSetting(string sKey, string sValue)
        {
            try
            {
                var keyItem = (from setting in remindersDB.Settings
                               where setting.Key == sKey
                               select setting).Single();

                keyItem.Value = sValue;

                remindersDB.SubmitChanges();
            }
            catch
            {
                DialogResult = DialogResult.Abort; // Close and propagate error to caller 
            }
        }

        private void btTestWS_Click(object sender, EventArgs e)
        {
            if (edTestMobile.Text.Length < 9)
                MessageBox.Show("Debe especificar un número de teléfono para enviar el SMS de prueba.",
                    "Configuración Movistar SMS", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);

            MovistarGateway.SendMessage(edServiceURL.Text, edServiceMobile.Text, edServicePass.Text, 
                edTestMobile.Text, "Mensaje de prueba desde Movistar SMS");
        }

        private void edMobile_KeyPress(object sender, KeyPressEventArgs e)
        {
            if (!((e.KeyChar == (char)8) || ((e.KeyChar >= (char)'0') && (e.KeyChar <= (char)'9'))))
                e.KeyChar = (char)0;
        }

        #endregion
    }
}
